﻿namespace _5_NovaAdmin.Infrastructure;

[AppStartup(100)]
public class Startup : AppStartup
{
    public IConfiguration config { get; set; }
    public override void ConfigureServices(IServiceCollection services)
    {
        if (services == null) throw new ArgumentNullException(nameof(services));
        services.AddUseContext();
        //注入Uow依赖 限定了DbContext和UnitOfWork的生命周期为Scoped，整个调用链上使用的数据库上下文对象，使用是同一个类型实例
        services.AddScoped<IUnitOfWork, UnitOfWork<AppDbContext>>();

        //注入泛型仓储
        services.AddTransient(typeof(IRepository<>), typeof(Repository<>));
        services.AddTransient(typeof(IRepository<,>), typeof(Repository<,>));
        services.AddTransient(typeof(ICompositeRepository<>), typeof(CompositeRepository<>));
        services.AddTransient(typeof(ICompositeRepository<,>), typeof(CompositeRepository<,>));

        services.AddCap(options =>
        {
            // 存储配置
            options.UseEntityFramework<AppDbContext>();

            // RabbitMQ 配置
            options.UseRabbitMQ(rabbitOptions =>
            {
                config.GetSection("RabbitMQ").Bind(rabbitOptions);
            });

            options.UseDashboard(); // 启用仪表盘
                                    //options.FailedRetryCount = 3;
                                    // 当重试次数达到FailedRetryCount（默认为50次）时，重试会停止
            options.FailedRetryInterval = 10; // 设置每次重试间隔为30秒
                                              //在消息发送或消费过程中，如果发生失败，CAP会立即重试3次，然后在FallbackWindowLookbackSeconds指定的时间后开始轮询重试
            options.FallbackWindowLookbackSeconds = 120; // 设置重试窗口时间为120秒
            options.SucceedMessageExpiredAfter = 180 * 24 * 3600; // 成功消息保留 24 小时
            options.FailedMessageExpiredAfter = 360 * 24 * 3600; // 失败消息保留 7 天
        });

        //services.AddSingleton<RedisClient>();
        services.AddSingleton(sp =>
        {
            var redisConfig = config.GetSection("RedisConfig");
            var section = new
            {
                Host = redisConfig["Host"],
                Port = redisConfig["Port"],
                Password = redisConfig["Password"],
                Database = redisConfig["Database"],
                Ssl = redisConfig["Ssl"],
                AbortOnConnectFail = redisConfig["AbortOnConnectFail"],
                ConnectTimeout = redisConfig["ConnectTimeout"],
                ConnectRetry = redisConfig["ConnectRetry"]
            };
            return new RedisClient(section);
        });
        //// 注册 Redis 数据库实例（可选）
        //services.AddSingleton(sp => sp.GetRequiredService<IConnectionMultiplexer>().GetDatabase());
        services.AddScoped<MigrationHandler>();

    }

    public override void Configure(IApplicationBuilder app)
    {
        app.MigrationDatabase();
    }
}
